
package org.eclipse.mylyn.rememberthemilk.core;

import java.net.MalformedURLException;

import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.Status;
import org.eclipse.mylyn.rememberthemilk.core.exceptions.RTMException;
import org.eclipse.mylyn.rememberthemilk.core.exceptions.RTMLoginException;
import org.eclipse.mylyn.rememberthemilk.core.exceptions.RTMPermissionDeniedException;
import org.eclipse.mylyn.tasks.core.RepositoryStatus;

/**
 * A convenience helper that wraps the ILog interface and provides status
 * creation methods.
 *
 */
public class RTMLog {

	/**
	 * Generate Info log messages
	 * @param message The message to display
	 */
	public static void logInfo(String message) {
		log(IStatus.INFO, IStatus.OK, message, null);
	}

	/**
	 * Generate an Error log message with a generic message
	 * @param exception Exception that generated the error
	 */
	public static void logError(Throwable exception) {
		logError("Unexpected Exception", exception);
	}

	/**
	 * Generate an Error log message with a supplied message and
	 * exception.
	 * @param message The readable message
	 * @param exception The exception that caused the error
	 */
	public static void logError(String message, Throwable exception) {
		log(IStatus.ERROR, IStatus.OK, message, exception);
	}

	/**
	 * Log a status based on supplied parameters
	 * @param severity The severity of the status
	 * @param code The code of the status
	 * @param message The readable message for the status
	 * @param exception An optional exception for the status
	 */
	public static void log(int severity, int code, String message,
			Throwable exception) {
		log(createStatus(severity, code, message, exception));
	}

	/**
	 * Log a RepositoryStatus for the supplied repositoryURL and other
	 * parameters.
	 * @param repositoryURL The URL for the task repository
	 * @param severity The severity of the status
	 * @param code The code for the status
	 * @param message The readable message for the status
	 * @param exception An optional exception for the status
	 */
	public static void log(String repositoryURL, int severity, int code,
			String message, Throwable exception) {
		log(createStatus(repositoryURL, severity, code, message,
				exception));
	}

	/**
	 * Create a IStatus based on the supplied parameters.
	 * @param severity The severity of the status
	 * @param code The code for the status
	 * @param message The readable message for the status
	 * @param exception An optional exception for the status
	 * @return An instantiated RepositoryStatus
	 */
	public static IStatus createStatus(int severity,
			int code, String message, Throwable exception) {
		return createStatus(null, severity, code, message, exception);
	}

	/**
	 * Create a RepositoryStatus based on the supplied parameters.
	 * @param repositoryURL Optional URL for the task repository
	 * @param severity The severity of the status
	 * @param code The code for the status
	 * @param message The readable message for the status
	 * @param exception An optional exception for the status
	 * @return An instantiated RepositoryStatus
	 */
	public static IStatus createStatus(String repoURL, int severity,
			int code, String message, Throwable exception) {
		if (repoURL != null) {
			return new RepositoryStatus(repoURL, severity,
					RTMCorePlugin.PLUGIN_ID, code, message, exception);
		} else {
			return new RepositoryStatus(severity, RTMCorePlugin.PLUGIN_ID,
					code, message, exception);
		}
	}

	/**
	 * Creates a IStatus based on the type of exception.  This was code
	 * that was originally found in the RTMCorePlugin.toStatus() method.
	 * @param exception
	 * @param repositoryUrl
	 * @return The instantiated IStatus
	 */
	public static IStatus createStatus(Throwable exception,
			String repositoryUrl) {
		if (exception instanceof RTMLoginException) {
			return RepositoryStatus.createLoginError(
					repositoryUrl, RTMCorePlugin.PLUGIN_ID);
		} else if (exception instanceof RTMPermissionDeniedException) {
			return createStatus(repositoryUrl, IStatus.ERROR,
					RepositoryStatus.ERROR_PERMISSION_DENIED,
					"Permission denied.", exception);
		} else if (exception instanceof RTMException) {
			String message = exception.getMessage();
			if (message == null) {
				message = "I/O error has occured";
			}
			return createStatus(repositoryUrl, Status.ERROR,
					RepositoryStatus.ERROR_IO,
					message, exception);
		} else if (exception instanceof ClassCastException) {
			return createStatus(Status.ERROR, RepositoryStatus.ERROR_IO,
					"Unexpected server response: " + exception.getMessage(),
					exception);
		} else if (exception instanceof MalformedURLException) {
			return createStatus(Status.ERROR, RepositoryStatus.ERROR_IO,
					"Repository URL is invalid", exception);
		} else {
			return createStatus(Status.ERROR, RepositoryStatus.ERROR_INTERNAL,
					"Unexpected error", exception);
		}
	}

	/**
	 * Create an IStatus with a severity of Status.ERROR, and populated based
	 * on the supplied parameters.
	 * @param repositoryURL Optional URL for the task repository
	 * @param code The code for the status
	 * @param message The readable message for the status
	 * @param exception An optional exception for the status
	 * @return An instantiated IStatus
	 */
	public static IStatus createErrorStatus(String repositoryURL, int code,
			String message, Throwable exception) {
		return createStatus(repositoryURL, Status.ERROR, code, message,
				exception);
	}

	/**
	 * Convenience method to use the default logger for the plugin.
	 * @param status The IStatus to log
	 */
	public static void log(IStatus status) {
		RTMCorePlugin.getDefault().getLog().log(status);
	}
}
